package org.proxycine.gestsalles.model.dao;

import java.sql.Date;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.sql.Time;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;

import org.proxycine.gestsalles.model.entities.CinemaComparator;
import org.proxycine.gestsalles.model.entities.Copie;
import org.proxycine.gestsalles.model.entities.DateComparator;
import org.proxycine.gestsalles.model.entities.Format_seance;
import org.proxycine.gestsalles.model.entities.GenreFilm;
import org.proxycine.gestsalles.model.entities.Langue_seance;
import org.proxycine.gestsalles.model.entities.Salle;
import org.proxycine.gestsalles.model.entities.Seance;
import org.proxycine.gestsalles.model.entities.Cinema;
import org.proxycine.gestsalles.model.entities.TypeSpectateur;
import org.proxycine.gestsalles.services.CinemaService;

public class SeanceDao extends Adapter {
	
		// un jour = 86 400 000 millisecondes
		final private int UN_JOUR = 86400000;
		
        private static SeanceDao instance;
        
        private SeanceDao() {
                instance = this;
        }
        
        public static SeanceDao getInstance() {
                if(instance == null)
                        instance = new SeanceDao();
                
                return instance;
        }
        
        public Seance insertSeance(Copie copie, Salle salle, Time debutSeance, Date date_seance, Langue_seance langue, Format_seance format )
        {
                ResultSet generatedKeys = null;
                int idSeance = -1;
                try {
                        PreparedStatement stmt = getConnection()
                                        .prepareStatement(
                                                        "INSERT INTO Seance (id, copie, salle, nombre_spectateur, nombre_spectateur_tarif_etudiants, nombre_spectateur_tarif_normal, nombre_spectateur_tarif_senior, debut_seance, date_seance, langue, format_seance)"
                                                                        + " VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", Statement.RETURN_GENERATED_KEYS);
                        
                        stmt.setString(1, null);
                        stmt.setInt(2, copie.getId());
                        stmt.setInt(3, salle.getId());
                        stmt.setString(4, null);
                        stmt.setString(5, null);
                        stmt.setString(6, null);
                        stmt.setString(7, null);
                        stmt.setTime(8, debutSeance);
                        stmt.setDate(9, date_seance);
                        stmt.setString(10, langue.toString());
                        stmt.setString(11, (format.toString()));
                        
                        stmt.executeUpdate();

                        generatedKeys = stmt.getGeneratedKeys();
                        
                        if (generatedKeys.next()) {
                                idSeance = generatedKeys.getInt(1);
                        } else {
                                throw new SQLException(
                                                "Creating film failed, no generated key obtained.");
                        }
                } catch (SQLException e) {
                        e.printStackTrace();
                }finally {
                        if (generatedKeys != null)
                                try {
                                        generatedKeys.close();
                                } catch (SQLException logOrIgnore) {}
                }

                return new Seance(idSeance, copie, salle, 0, 0, 0, 0, debutSeance, date_seance, langue, format);
        }
        
    	public void removeSeance(int id) {
    		
    		try {
    			PreparedStatement stmt = getConnection()
    						.prepareStatement("DELETE from Seance where id = ?");
    			stmt.setInt(1, id);
    			stmt.executeUpdate();
    		}
    		catch (SQLException e) {
    			e.printStackTrace();
    		}
    	}
        
        public List<Seance> getProjectionsForLoggedManager(String managerLogin)
        {
                List<Seance> seances = new ArrayList<Seance>();
                String request = "SELECT Se.* " +
                                "FROM Seance Se, Salle Sa, Cinema C, Employe E " +
                                "WHERE E.login = C.gerant " +
                                "AND Sa.cinema = C.id " +
                                "AND Se.salle = Sa.id " +
                                "AND E.login = '"+ managerLogin + "'";
                                
                                try {
                                        ResultSet rs = getStatement().executeQuery(request);
                                        
                                        while (rs.next()) {
                                                seances.add(new Seance(rs.getInt("id"),
                                                                CopieDao.getInstance().getCopieFromId(rs.getInt("copie")),
                                                                SalleDao.getInstance().getSalleFromId(rs.getInt("salle")),
                                                                rs.getInt("nombre_spectateur"),
                                                                rs.getInt("nombre_spectateur_tarif_etudiants"),
                                                                rs.getInt("nombre_spectateur_tarif_normal"),
                                                                rs.getInt("nombre_spectateur_tarif_senior"),
                                                                rs.getTime("debut_seance"),
                                                                rs.getDate("date_seance"),
                                                                Langue_seance.valueOf(rs.getString("langue")),
                                                                Format_seance.valueOf(rs.getString("format_seance"))));
                                        }
                                        
                                        rs.close();
                                        
                                } catch (SQLException e) {
                                        e.printStackTrace();
                                }               
                return seances;
                
        }
        
        public List<Seance> getProjectionInOneRoomForLoggedManager(String managerLogin, Salle roomNumber)
        {
                List<Seance> seances = new ArrayList<Seance>();
                String request = "SELECT Se.* " +
                                "FROM Seance Se, Salle Sa, Cinema C, Employe E " +
                                "WHERE E.login = C.gerant " +
                                "AND Sa.cinema = C.id " +
                                "AND Se.salle = Sa.id " +
                                "AND E.login = '"+ managerLogin + "' " +
                                "AND SA.numero_salle = '" + roomNumber +"'";
                                
                                try {
                                        ResultSet rs = getStatement().executeQuery(request);
                                        
                                        while (rs.next()) {
                                                seances.add(new Seance(rs.getInt("id"),
                                                                CopieDao.getInstance().getCopieFromId(rs.getInt("copie")),
                                                                SalleDao.getInstance().getSalleFromId(rs.getInt("salle")),
                                                                rs.getInt("nombre_spectateur"),
                                                                rs.getInt("nombre_spectateur_tarif_etudiants"),
                                                                rs.getInt("nombre_spectateur_tarif_normal"),
                                                                rs.getInt("nombre_spectateur_tarif_senior"),
                                                                rs.getTime("debut_seance"),
                                                                rs.getDate("date_seance"),
                                                                Langue_seance.valueOf(rs.getString("langue")),
                                                                Format_seance.valueOf(rs.getString("format_seance"))));
                                        }
                                        
                                        rs.close();
                                        
                                } catch (SQLException e) {
                                        e.printStackTrace();
                                }               
                return seances;
                
        }
        
        
        /*
         *  Requêtes pour le tableau de bord du réseau
         */
                
        /**
         *  calcule l’affluence par cinémas en fonction du temps
         *  
         * @param dateDebut
         * @param dateFin
         * 
         * @return le nombre d'entrée par cinéma et par date
         */
        public Map<Cinema, Map<Date,Integer> > getAffluenceReseauParCinema(String dateDebut, String dateFin) {

        	Map<Cinema, Map<Date,Integer> > affluence = populateCinemasDates(dateDebut, dateFin);
        	
        	        	
        	String request = "SELECT Ci.id, S.date_seance, SUM(S.nombre_spectateur) AS total " +
								"FROM Copie Co, Cinema Ci, Seance S " +
								"WHERE Co.cinema = Ci.id " +
								"AND S.copie = Co.id " +
								"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
								"GROUP BY Ci.id, S.date_seance " +
								"ORDER BY Ci.id, S.date_seance";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    Cinema currentCinema = null;
			    while (rs.next()) {
			    	currentCinema = CinemaService.getInstance().getCinema(rs.getInt("id"));
			    	affluence.get(currentCinema).put(rs.getDate("date_seance"),	rs.getInt("total"));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return affluence;
        }
        
        
        /**
         * calcule l’affluence de l’ensemble des cinémas en fonction du genre de film et du temps 
         * 
         * @param dateDebut
         * @param dateFin
         * 
         * @return le nombre d'entrée par genre et par date
         */
        public Map<GenreFilm, Map<Date, Integer> > getAffluenceReseauParGenre(String dateDebut, String dateFin) {
        	Map<GenreFilm, Map<Date, Integer> > affluence = populateGenresDates(dateDebut, dateFin);
        	
        	
        	String request = "SELECT F.genre, S.date_seance, SUM(S.nombre_spectateur) AS total " +
								"FROM Film F, Copie Co, Seance S " +
								"WHERE Co.film = F.id " +
								"AND S.copie = Co.id " +
								"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
								"GROUP BY F.genre, S.date_seance " +
								"ORDER BY F.genre, S.date_seance";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    GenreFilm currentGenre = null;
			    while (rs.next()) {
			    	currentGenre = GenreFilm.valueOf(rs.getString("genre"));
			    	affluence.get(currentGenre).put(rs.getDate("date_seance"), rs.getInt("total"));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return affluence;
        }
        
        /**
         * calcule l’affluence de l’ensemble des cinémas en fonction de la catégorie spectateur et du temps
         * @param dateDebut
         * @param dateFin
         * 
         * @return le nombre d'entrée par catégorie de spectateur et par date
         */
        public Map<TypeSpectateur, Map<Date, Integer> > getAffluenceReseauParCategorieSpec(String dateDebut, String dateFin) {
        	Map<TypeSpectateur, Map<Date, Integer> > affluence = populateSpectateursDates(dateDebut, dateFin);
        	
        	String request = "SELECT T.nom, S.date_seance, " + 
		        			"SUM(S.nombre_spectateur_tarif_etudiants) AS Étudiant, " +
		        			"SUM(S.nombre_spectateur_tarif_normal) AS Normal, " +
		        			"SUM(S.nombre_spectateur_tarif_senior) AS Senior " +
	        			"FROM Film F, Copie Co, Seance S, Tarif T " +
		        		"WHERE Co.film = F.id " +
		        		"AND S.copie = Co.id " +
		        		"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
		        		"GROUP BY T.nom, S.date_seance " +
		        		"ORDER BY T.nom, S.date_seance";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    TypeSpectateur currentType = null;
			    
			    while (rs.next()) {
			    	currentType = TypeSpectateur.valueOf(rs.getString("nom"));
			    				    		
			    	affluence.get(currentType).put(rs.getDate("date_seance"), rs.getInt(currentType.name()));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return affluence;
        }
        
        /**
         *  calcule la part d’affluence de chaque cinéma du réseau
         * 
         * @param dateDebut
         * @param dateFin
         * 
         * @return  le % d’entrée par cinéma
         */
        public Map<Cinema, Integer> getPartAffluenceReseauParCinema(String dateDebut, String dateFin) {
        	Map<Cinema, Integer> partsAffluence = populateCinemas();
        	
        	String request = "SELECT Ci.id, " +
        				"(SUM(S.nombre_spectateur) / " + 
        				"(SELECT SUM(S2.nombre_spectateur) " + 
        					"FROM Seance S2 " +
        					"WHERE S2.date_seance " +
        					"BETWEEN '"+dateDebut+"' AND '"+dateFin+"') ) * 100 AS pourcentage " +

    					"FROM Copie Co, Cinema Ci, Seance S " +
    					"WHERE Co.cinema = Ci.id " +
    					"AND S.copie = Co.id " +
    					"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
    					"GROUP BY Ci.id " +
    					"ORDER BY Ci.id ";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    Cinema currentCinema = null;
			    
			    while (rs.next()) {
			    	currentCinema = CinemaService.getInstance().getCinema(rs.getInt("id"));
			    	partsAffluence.put(currentCinema, rs.getInt("pourcentage"));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return partsAffluence;
        }
        
        /**
         * calcule la part d’affluence de chaque genre de film sur le réseau
         * 
         * @param dateDebut
         * @param dateFin
         * 
         * @return  le % d’entrée par genre
         */
        public Map<GenreFilm, Integer> getPartAffluenceReseauParGenre(String dateDebut, String dateFin) {
        	Map<GenreFilm, Integer> partsAffluence = populateGenres(dateDebut, dateFin);
        	
        	String request = "SELECT F.genre, " +
        					"(SUM(S.nombre_spectateur) / " + 
        						"(SELECT SUM(S2.nombre_spectateur) " + 
        							"FROM Seance S2 " +
        							"WHERE S2.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"') ) * 100 AS pourcentage " +

        					"FROM Film F, Copie Co, Seance S " +
        					"WHERE Co.film = F.id " +
        					"AND S.copie = Co.id " +
        					"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
        					"GROUP BY F.genre " +
        					"ORDER BY F.genre";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    GenreFilm currentGenre = null;
			    
			    while (rs.next()) {
			    	currentGenre = GenreFilm.valueOf(rs.getString("genre"));			    	
			    	partsAffluence.put(currentGenre, rs.getInt("pourcentage"));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return partsAffluence;
        }
        

        /**
         * calcule la part d’affluence de chaque catégorie de spectateur sur le réseau
         * 
         * @param dateDebut
         * @param dateFin
         * 
         * @return  le % d’entrée par catégorie de spectateur
         */
        public Map<TypeSpectateur, Integer> getPartAffluenceReseauParCategorieSpec(String dateDebut, String dateFin) {
        	Map<TypeSpectateur, Integer> partsAffluence = populateTypesSpectateurs(dateDebut, dateFin);
        	
        	String request = "SELECT T.nom, " + 
        			"(SUM(S.nombre_spectateur_tarif_etudiants) / (SUM(S.nombre_spectateur_tarif_etudiants) + SUM(S.nombre_spectateur_tarif_normal) + SUM(S.nombre_spectateur_tarif_senior)))*100 AS Étudiant, " +
        			
        			"(SUM(S.nombre_spectateur_tarif_normal) / (SUM(S.nombre_spectateur_tarif_etudiants) + SUM(S.nombre_spectateur_tarif_normal) + SUM(S.nombre_spectateur_tarif_senior)))*100 AS Normal, " +
        			
        			"(SUM(S.nombre_spectateur_tarif_senior) / (SUM(S.nombre_spectateur_tarif_etudiants) + SUM(S.nombre_spectateur_tarif_normal) + SUM(S.nombre_spectateur_tarif_senior)))*100 AS Senior " +
        		"FROM Film F, Copie Co, Seance S, Tarif T " +
        		"WHERE Co.film = F.id " +
        		"AND S.copie = Co.id " +
        		"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
        		"GROUP BY T.nom";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    TypeSpectateur currentType = null;
			    
			    while (rs.next()) {
			    	currentType = TypeSpectateur.valueOf(rs.getString("nom"));
			    	partsAffluence.put(currentType, rs.getInt(currentType.name()));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return partsAffluence;
        }
        
        
        /*
         *  Requête pour le tableau de bord du cinéma
         */
        
        /**
         * calcule l’affluence d'un cinéma en fonction du temps
         * 
         * @param cinema
         * @param dateDebut
         * @param dateFin
         * 
         * @return le nombre d'entrée du cinéma par date
         */
        public Map<Date,Integer> getAffluenceCinema(Cinema cinema, String dateDebut, String dateFin) {
        	Map<Date,Integer> affluence = populateDates(dateDebut, dateFin);
        	        	
        	String request = "SELECT S.date_seance, SUM(S.nombre_spectateur) AS total " +
								"FROM Copie Co, Cinema Ci, Seance S " +
								"WHERE Co.cinema = " + cinema.getId() + " " +
								"AND S.copie = Co.id " +
								"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
								"GROUP BY Ci.id, S.date_seance " +
								"ORDER BY Ci.id, S.date_seance";

        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);

			    while (rs.next()) {
	    			affluence.put(rs.getDate("date_seance"), rs.getInt("total"));
		    	}
			    
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return affluence;
        }
        
        
        /**
         *  calcule l’affluence d'un cinéma en fonction du genre de film et du temps
         * 
         * @param cinema
         * @param dateDebut
         * @param dateFin
         * 
         * @return le nombre d'entrée du cinéma par genre de film et par date
         */
        public Map<GenreFilm, Map<Date,Integer> > getAffluenceCinemaParGenre(Cinema cinema, String dateDebut, String dateFin) {
        	Map<GenreFilm, Map<Date, Integer> > affluence = populateGenresDates(dateDebut, dateFin);
        	
        	
        	String request = "SELECT F.genre, S.date_seance, SUM(S.nombre_spectateur) AS total " +
								"FROM Film F, Copie Co, Seance S " +
								"WHERE Co.film = F.id " +
								"AND S.copie = Co.id " +
								"AND Co.cinema = " + cinema.getId() + " " +
								"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
								"GROUP BY F.genre, S.date_seance " +
								"ORDER BY F.genre, S.date_seance";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    GenreFilm currentGenre = null;
			    while (rs.next()) {
			    	currentGenre = GenreFilm.valueOf(rs.getString("genre"));
			    	affluence.get(currentGenre).put(rs.getDate("date_seance"), rs.getInt("total"));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			        	
        	return affluence;
        }
        
        
        /**
         * calcule l’affluence en fonction du type de spectateur et du temps
         * 
         * @param cinema
         * @param dateDebut
         * @param dateFin
         * 
         * @return le nombre d'entrée du cinéma par type de spectateur et par date
         */
        public Map<TypeSpectateur, Map<Date,Integer> > getAffluenceCinemaParCategorieSpec(Cinema cinema, String dateDebut, String dateFin) {
        	Map<TypeSpectateur, Map<Date, Integer> > affluence = populateSpectateursDates(dateDebut, dateFin);
        	
        	String request = "SELECT T.nom, S.date_seance, " + 
		        			"SUM(S.nombre_spectateur_tarif_etudiants) AS Étudiant, " +
		        			"SUM(S.nombre_spectateur_tarif_normal) AS Normal, " +
		        			"SUM(S.nombre_spectateur_tarif_senior) AS Senior " +
	        			"FROM Film F, Copie Co, Seance S, Tarif T " +
		        		"WHERE Co.film = F.id " +
		        		"AND S.copie = Co.id " +
		        		"AND Co.cinema = " + cinema.getId() + " " +
		        		"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
		        		"GROUP BY T.nom, S.date_seance " +
		        		"ORDER BY T.nom, S.date_seance";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    TypeSpectateur currentType = null;
			    
			    while (rs.next()) {
			    	currentType = TypeSpectateur.valueOf(rs.getString("nom"));
			    				    		
			    	affluence.get(currentType).put(rs.getDate("date_seance"), rs.getInt(currentType.name()));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return affluence;
        }
        
        /**
         * calcule la part d’affluence de chaque genre de film pour un cinéma
         * 
         * @param cinema
         * @param dateDebut
         * @param dateFin
         * 
         * @return le % d’entrée par genre
         */
        public Map<GenreFilm, Integer> getPartAffluenceCinemaParGenre(Cinema cinema, String dateDebut, String dateFin) {
        	Map<GenreFilm, Integer> partsAffluence = populateGenres(dateDebut, dateFin);
        	
        	String request = "SELECT F.genre, " +
        					"(SUM(S.nombre_spectateur) / " + 
        						"(SELECT SUM(S2.nombre_spectateur) " + 
        							"FROM Seance S2 " +
        							"WHERE S2.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"') ) * 100 AS pourcentage " +

        					"FROM Film F, Copie Co, Seance S " +
        					"WHERE Co.film = F.id " +
        					"AND S.copie = Co.id " +
        					"AND Co.cinema = " + cinema.getId() + " " +
        					"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
        					"GROUP BY F.genre " +
        					"ORDER BY F.genre";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    GenreFilm currentGenre = null;
			    
			    while (rs.next()) {
			    	currentGenre = GenreFilm.valueOf(rs.getString("genre"));			    	
			    	partsAffluence.put(currentGenre, rs.getInt("pourcentage"));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return partsAffluence;
        }
        
        /**
         * calcule la part d’affluence de chaque catégorie de spectateur pour un cinéma
         * 
         * @param cinema
         * @param dateDebut
         * @param dateFin
         * 
         * @return le % d’entrée par catégorie de spectateur
         */
        public Map<TypeSpectateur, Integer> getPartAffluenceCinemaParCategorieSpec(Cinema cinema, String dateDebut, String dateFin) {
        	Map<TypeSpectateur, Integer> partsAffluence = populateTypesSpectateurs(dateDebut, dateFin);
        	
        	String request = "SELECT T.nom, " + 
        			"(SUM(S.nombre_spectateur_tarif_etudiants) / (SUM(S.nombre_spectateur_tarif_etudiants) + SUM(S.nombre_spectateur_tarif_normal) + SUM(S.nombre_spectateur_tarif_senior)))*100 AS Étudiant, " +
        			
        			"(SUM(S.nombre_spectateur_tarif_normal) / (SUM(S.nombre_spectateur_tarif_etudiants) + SUM(S.nombre_spectateur_tarif_normal) + SUM(S.nombre_spectateur_tarif_senior)))*100 AS Normal, " +
        			
        			"(SUM(S.nombre_spectateur_tarif_senior) / (SUM(S.nombre_spectateur_tarif_etudiants) + SUM(S.nombre_spectateur_tarif_normal) + SUM(S.nombre_spectateur_tarif_senior)))*100 AS Senior " +
        		"FROM Film F, Copie Co, Seance S, Tarif T " +
        		"WHERE Co.film = F.id " +
        		"AND S.copie = Co.id " +
        		"AND Co.cinema = " + cinema.getId() + " " +
        		"AND S.date_seance BETWEEN '"+dateDebut+"' AND '"+dateFin+"' " +
        		"GROUP BY T.nom";
        	
			try {
			    ResultSet rs = getStatement().executeQuery(request);
			    TypeSpectateur currentType = null;
			    
			    while (rs.next()) {
			    	currentType = TypeSpectateur.valueOf(rs.getString("nom"));
			    	partsAffluence.put(currentType, rs.getInt(currentType.name()));
		        }
			        
		        rs.close();
			        
			} catch (SQLException e) {
			        e.printStackTrace();
			}
			
        	return partsAffluence;
        }
        

        /*
         * 
         * Fonctions pour insérer des données "vierges" dans les Maps
         * 
         */
        public Map<Cinema, Integer> populateCinemas() {
        	Map<Cinema, Integer> map = new TreeMap<Cinema, Integer>(new CinemaComparator()); 
        	
        	List<Cinema> lesCines = CinemaService.getInstance().getAllCinemas();
			
        	for (Cinema c : lesCines) {
        		map.put(c, 0);
        	}
			
			return map;
        }
        
        public Map<GenreFilm, Integer> populateGenres(String dateDebut, String dateFin) {
        	Map<GenreFilm, Integer> map = new TreeMap<GenreFilm, Integer>(); 
        				
        	for (GenreFilm genre : GenreFilm.values()) {
        		map.put(genre, 0);
        	}
			
			return map;
        }
        
        public Map<TypeSpectateur, Integer> populateTypesSpectateurs(String dateDebut, String dateFin) {
        	Map<TypeSpectateur, Integer> map = new TreeMap<TypeSpectateur, Integer>(); 
        				
        	for (TypeSpectateur type : TypeSpectateur.values()) {
        		map.put(type, 0);
        	}
			
			return map;
        }
        
        public Map<GenreFilm, Map<Date,Integer> > populateGenresDates(String dateDebut, String dateFin) {
        	Map<GenreFilm, Map<Date,Integer> > map = new TreeMap<GenreFilm, Map<Date, Integer>>(); 
        				
        	for (GenreFilm genre : GenreFilm.values()) {
        		map.put(genre, populateDates(dateDebut, dateFin));
        	}
			
			return map;
        }
        
        public Map<TypeSpectateur, Map<Date,Integer> > populateSpectateursDates(String dateDebut, String dateFin) {
        	Map<TypeSpectateur, Map<Date,Integer> > map = new TreeMap<TypeSpectateur, Map<Date, Integer>>(); 
        				
        	for (TypeSpectateur typeSpectateur : TypeSpectateur.values()) {
        		map.put(typeSpectateur, populateDates(dateDebut, dateFin));
        	}
			
			return map;
        }
        
        public Map<Cinema, Map<Date,Integer> > populateCinemasDates(String dateDebut, String dateFin) {
        	Map<Cinema, Map<Date,Integer> > map = new TreeMap<Cinema, Map<Date, Integer>>(new CinemaComparator()); 
        	
        	List<Cinema> lesCines = CinemaService.getInstance().getAllCinemas();
			
        	for (Cinema c : lesCines) {
        		map.put(c, populateDates(dateDebut, dateFin));
        	}
			
			return map;
        }
        
        
        public Map<Date,Integer> populateDates(String dateDebut, String dateFin) {
        	Map<Date, Integer> map = new TreeMap<Date, Integer>(new DateComparator());

			java.sql.Date sqlDateDebut = Date.valueOf(dateDebut);
			java.sql.Date sqlDateFin = Date.valueOf(dateFin);
			
			while (sqlDateDebut.compareTo(sqlDateFin) <= 0) {
				map.put((Date)sqlDateDebut.clone(), 0);
				sqlDateDebut.setTime(sqlDateDebut.getTime() + UN_JOUR);
			}
			
			return map;
        }
}
